#include "mainwindow.h"
#include "ui_mainwindow.h"
#include"hill_cipher.h"
#include<QDebug>
#include<QDialog>
#include<QPushButton>
#include<QTextEdit>
#include<QScreen>
MainWindow::MainWindow(QWidget *parent) :
    QMainWindow(parent),
    ui(new Ui::MainWindow)
{
    ui->setupUi(this);
    this->setWindowIcon(QIcon(":/key_lock"));
    setWindowTitle("Hill密码实验");
    this->setFixedSize(this->size());
    iniSignal();
}

void MainWindow::iniSignal()
{
    connect(ui->pushButton,SIGNAL(clicked()),this,SLOT(encrypt()));
    connect(ui->pushButton_2,SIGNAL(clicked()),this,SLOT(decrypt()));

}

void MainWindow::encrypt()
{
    QString plainText1 = ui->plainTextEdit->toPlainText();
    std::string s1 = plainText1.toStdString();
    int plainLength1 = plainText1.length();
    if(plainLength1>0)
    {
        //判断明文是否全为小写字母
        if(Hill_Cipher::includeOtherChar(s1))
        {
            std::string ciphertext;
            Hill_Cipher hh(plainLength1);
            //判断是否使用随机秘钥
            if(ui->checkBox->checkState() == Qt::Checked)
            {
                if(plainLength1>7)
                {
                    QDialog *dialogWarning = new QDialog(this);
                    dialogWarning->resize(200,85);
                    dialogWarning->setWindowTitle("Warning");
                    dialogWarning->setFixedSize(dialogWarning->size());
                    dialogWarning->setModal(true);
                    QTextEdit * textWarning = new QTextEdit(tr("只支持随机生成大小为7*7及以下的秘钥"),dialogWarning);
                    QFont textFont;
                    textFont.setBold(true); //设置文字为粗体
                    textFont.setPointSize(11);//设置文字大小
                    textWarning->setFont(textFont);
                    textWarning->resize(200,50);
                    textWarning->setReadOnly(true);
                    QPalette pl = textWarning->palette();
                    pl.setBrush(QPalette::Base,QBrush(QColor(255,0,0,0)));//文本框透明
                    textWarning->setPalette(pl);
                    QPushButton * buttonWarning = new QPushButton(tr("确定"),dialogWarning);
                    buttonWarning->move(125,60);
                    connect(buttonWarning,SIGNAL(clicked()),dialogWarning,SLOT(close()));
                    dialogWarning->show();
                    return;
                }

                srand((unsigned)time(0));
                hh.creatRMatrix(plainLength1);
                while (!hh.ifInverse(hh.K))
                    hh.creatRMatrix(plainLength1);
            }
            else
            {   //将秘钥字符串输入秘钥数组
                QString plainText2 = ui->plainTextEdit_2->toPlainText();
                if(plainText2.length()>0)
                {
                    std::string s2 = plainText2.toStdString();
                    //判断秘钥长度是否符合
                    if(plainText2.length()==plainLength1*plainLength1)
                    {
                        //将窗口输入的秘钥输入秘钥数组
                        hh.stringToK(s2);
                        //判断窗口输入的秘钥是否符合条件，符合后执行加密动作
                        if(!hh.ifInverse(hh.K))
                        {
                            ui->plainTextEdit_3->setPlainText(tr("秘钥格式错误"));
                            return;
                        }

                    }
                    else
                    {
                        ui->plainTextEdit_3->setPlainText(tr("秘钥格式错误"));
                        return;
                    }
                }
                else
                {
                    ui->plainTextEdit_3->setPlainText(tr("请输入秘钥"));
                    return;
                }

            }
            ciphertext=hh.encryption(s1);
            ui->plainTextEdit_3->setPlainText(QString::fromStdString(ciphertext));
            ui->plainTextEdit_2->setPlainText(QString::fromStdString( hh.KtoString()));

        }
        else
        {
            ui->plainTextEdit_3->setPlainText(tr("明文格式错误，使用小写英文字母作为明文"));

        }
    }
    else
    {
        ui->plainTextEdit->setPlainText(tr("请在这里输入需要加密的明文!"));
    }
}

void MainWindow::decrypt()
{
    QString plainText3 = ui->plainTextEdit_3->toPlainText();
    int plainLength3 = plainText3.length();
    QString plainText2 = ui->plainTextEdit_2->toPlainText();
    int plainLength2 = plainText2.length();
    if(plainLength3 > 0)
    {
        std::string s3= plainText3.toStdString();
        //判断密文中是否全部为大写字母
        if(Hill_Cipher::includeOtherChar1(s3))
        {
            if(plainLength3>7)
            {
                QDialog *dialogWarning = new QDialog(this);
                dialogWarning->resize(200,85);
                dialogWarning->setWindowTitle("Warning");
                dialogWarning->setFixedSize(dialogWarning->size());
                dialogWarning->setModal(true);
                QTextEdit * textWarning = new QTextEdit(tr("为了便于检验正确性，只支持7位及以下的密文解密"),dialogWarning);
                QFont textFont;
                textFont.setBold(true); //设置文字为粗体
                textFont.setPointSize(11);//设置文字大小
                textWarning->setFont(textFont);
                textWarning->resize(200,50);
                textWarning->setReadOnly(true);
                QPalette pl = textWarning->palette();
                pl.setBrush(QPalette::Base,QBrush(QColor(255,0,0,0)));//文本框透明
                textWarning->setPalette(pl);
                QPushButton * buttonWarning = new QPushButton(tr("确定"),dialogWarning);
                buttonWarning->move(125,60);
                connect(buttonWarning,SIGNAL(clicked()),dialogWarning,SLOT(close()));
                dialogWarning->show();
                return;

            }

            std::string s2 = plainText2.toStdString();
            //判断秘钥长度是否符合
            if(plainLength2==plainLength3*plainLength3)
            {
                Hill_Cipher dd(plainLength3);
                dd.stringToK(s2);
                //判断秘钥是否符合
                if(dd.ifInverse(dd.K))
                {
                    dd.stringToC(s3);
                    std::string s1=dd.deciphering();
                    qDebug()<<QString::fromStdString(s1)<<endl;
                    //ui->plainTextEdit->clear();
                    ui->plainTextEdit->setPlainText(QString::fromStdString(s1));
                }
                else
                {
                    ui->plainTextEdit->setPlainText(tr("秘钥格式错误"));

                }
            }

            else
            {
                ui->plainTextEdit->setPlainText(tr("秘钥格式错误"));
            }
        }
        else
        {
            ui->plainTextEdit->setPlainText(tr("密文格式错误，使用大写英文字母作为密文"));
        }
    }
    else
    {
        ui->plainTextEdit->setPlainText(tr("请输入密文！"));
    }

}



MainWindow::~MainWindow()
{
    delete ui;
}

void MainWindow::on_actionauthor_triggered()
{
    QDialog * dialog = new QDialog(this);
    dialog-> setWindowTitle("作者");
    dialog->setFixedSize(150,150);
    QPushButton *button = new QPushButton(tr("确定"),dialog);
    connect(button,SIGNAL(clicked()),dialog,SLOT(close()));
    button->move(70,120);
    QTextEdit * Text_author = new QTextEdit(tr("作者：  XXXXXXXXX"),dialog);
    QFont font;
    font.setFamily("楷体");
    font.setPixelSize(50);//设置文字大小为50像素
    font.setBold(true); //设置文字为粗体
    font.setPointSize(19);//设置文字大小
    //font.setStyle(QFont::StyleItalic);//设置文字倾斜
    font.setWeight(QFont::Light);//设置文字粗细//enum Weight 存在5个值
    //font.setUnderline(true);//设置文字下划线
    font.setLetterSpacing(QFont::PercentageSpacing,300); //设置字间距%  300%,100为默认
    font.setLetterSpacing(QFont::AbsoluteSpacing,20); //设置字间距像素值
    Text_author->setFont( font);
    Text_author->setTextBackgroundColor(QColor('Black'));
    Text_author->setReadOnly(true);
    Text_author->resize(150,100);
    QPalette pl = Text_author->palette();
    pl.setBrush(QPalette::Base,QBrush(QColor(255,0,0,0)));//文本框透明
    Text_author->setPalette(pl);
    dialog->show();
}

void MainWindow::on_actionTips_triggered()
{
    QDialog * dialog = new QDialog(this);
    dialog-> setWindowTitle("提示");
    dialog->setFixedSize(400,150);
    QPushButton *button = new QPushButton(tr("确定"),dialog);
    button->move(300,100);
    connect(button,SIGNAL(clicked()),dialog,SLOT(close()));
    QLabel *linkLabel = new QLabel(dialog);
    linkLabel->setOpenExternalLinks(true);
    linkLabel->setText("<a href=\"https://baike.baidu.com/item/%E5%B8%8C%E5%B0%94%E5%AF%86%E7%A0%81\">加密原理详细介绍（点击访问百度百科）");
    linkLabel->move(80,40);
    QLabel *linkLabel_2 = new QLabel(dialog);
    linkLabel_2->setOpenExternalLinks(true);
    linkLabel_2->setText("<a href=\"http://www.practicalcryptography.com/ciphers/hill-cipher/#introduction\">practicalcryptography.com");
    linkLabel_2->move(80,80);
    dialog->show();
}
